package com.lee.mq.mqserver.core;

/**
 * Created with IntelliJ IDEA.
 * Description:
 * User: lishuo
 * Date: 2023-10-19
 * Time: 16:33
 */

import java.io.Serializable;
import java.util.Arrays;
import java.util.UUID;

/**
 * 表示传递消息的类
 * 此处的 Message 对象, 是需要能够在网络上传输, 并且也需要能写入到文件中.
 * 此时就需要针对 Message 进行序列化和反序列化.
 */
public class Message implements Serializable {
    // 两个核心属性
    // basicProperties 表示消息相关属性
    private BasicProperties basicProperties = new BasicProperties();
    // body 表示消息内容
    private byte[] body;

    // 辅助属性
    // [offsetBeg,offsetEnd) 定位消息在文件中的具体位置.
    // 这两个属性不需要序列化，因为这两个属性是为了让内存中的 Message 对象快速找到对应硬盘上的位置.
    private transient long offsetBeg = 0; // 消息数据的开头距离文件开头的位置偏移.
    private transient long offsetEnd = 0; // 消息数据的结尾距离文件开头的位置偏移.

    // isVailid 表示该消息在文件中是否有效（0x1 表示有效；0x0表示无效.类似于逻辑删除）
    private byte isVailid = 0x1;

    // createMessageWithId 表示一个工厂方法，用于封装创建 Message 对象的过程.
    public static Message createMessageWithId(String routingKey,BasicProperties basicProperties,byte[] body) {
        Message message = new Message();
        if (basicProperties != null) {
            message.setBasicProperties(basicProperties);
        }
        // 创建对象时自动生成唯一 messageId,以 M- 为前缀
        message.setMessageId("M-"+UUID.randomUUID());
        message.setRoutingKey(routingKey);
        message.setBody(body);

        // 上述创建 Message对象时，主要对核心属性 basicProperties ，body 进行设置.
        // offsetBeg，offsetEnd，isValid 是消息持久化时才会用到，将消息写入文件之前在设置.

        // 返回在内存中创建的 Message 对象
        return message;
    }

    public String getMessageId() {
        return basicProperties.getMessageId();
    }

    public void setMessageId(String messageId) {
        basicProperties.setMessageId(messageId);
    }

    public String getRoutingKey() {
        return basicProperties.getRoutingKey();
    }

    public void setRoutingKey(String routingKey) {
        basicProperties.setRoutingKey(routingKey);
    }

    public int getDeliverMode() {
        return basicProperties.getDeliverMode();
    }

    public void setDeliverMode(int mode) {
        basicProperties.setDeliverMode(mode);
    }

    public BasicProperties getBasicProperties() {
        return basicProperties;
    }

    public void setBasicProperties(BasicProperties basicProperties) {
        this.basicProperties = basicProperties;
    }

    public byte[] getBody() {
        return body;
    }

    public void setBody(byte[] body) {
        this.body = body;
    }

    public long getOffsetBeg() {
        return offsetBeg;
    }

    public void setOffsetBeg(long offsetBeg) {
        this.offsetBeg = offsetBeg;
    }

    public long getOffsetEnd() {
        return offsetEnd;
    }

    public void setOffsetEnd(long offsetEnd) {
        this.offsetEnd = offsetEnd;
    }

    public byte getIsVailid() {
        return isVailid;
    }

    public void setIsVailid(byte isVailid) {
        this.isVailid = isVailid;
    }

    @Override
    public String toString() {
        return "Message{" +
                "basicProperties=" + basicProperties +
                ", body=" + Arrays.toString(body) +
                ", offsetBeg=" + offsetBeg +
                ", offsetEnd=" + offsetEnd +
                ", isVailid=" + isVailid +
                '}';
    }
}
